package com.zhuoyue.biz.core.command.cmd.common.fe6;

import com.zhuoyue.biz.core.api.domain.DeviceAndGatewayDO;
import com.zhuoyue.biz.core.api.dto.req.ControlReq;
import com.zhuoyue.biz.core.command.cmd.common.fe6.base.AcModeEnum;
import com.zhuoyue.biz.core.command.cmd.common.fe6.base.AcSwitchEnum;
import com.zhuoyue.biz.core.command.cmd.common.fe6.base.AcWindDirectionEnum;
import com.zhuoyue.biz.core.command.cmd.common.fe6.base.AcWindSpeedEnum;
import com.zhuoyue.biz.core.command.constant.InfraredCmdDeal;
import com.zhuoyue.common.constant.ControlType;
import com.zhuoyue.common.utils.CmdUtils;
import com.zhuoyue.common.utils.DataTypeUtil;

import java.util.Map;

/**
 * @ClassName: HongWaiXueXiYi_0FE60202
 * @Description:
 * @author wjming
 * @Date 2021-07-14 20:19
 */
public class HongWaiXueXiYi0Fe60202 {
    public static String control(DeviceAndGatewayDO deviceAndGatewayDO, ControlReq controlReq) {
        String cmd = "";
        switch (controlReq.getControlType()) {
            //红外信号学习
            case ControlType.INFRARED_STUDY_REQUEST:
                cmd = getInfraredStudyCmd(deviceAndGatewayDO, controlReq);
                break;
            //红外信号发送
            case ControlType.INFRARED_SEND_REQUEST:
                cmd = getInfraredSendCmd(deviceAndGatewayDO, controlReq);
                break;
            //空调开关命令发送
            case ControlType.AC_SWITCH_SEND_REQUEST:
                cmd = getAcSwitchSendCmd(deviceAndGatewayDO, controlReq);
                break;
            //空调模式命令发送
            case ControlType.AC_MODE_SEND_REQUEST:
                cmd = getAcModeSendCmd(deviceAndGatewayDO, controlReq);
                break;
            //空调温度命令发送
            case ControlType.AC_TEMP_SEND_REQUEST:
                cmd = getAcTempSendCmd(deviceAndGatewayDO, controlReq);
                break;
            //空调风速命令发送
            case ControlType.AC_WIND_SPEED_SEND_REQUEST:
                cmd = getAcWindSpeedSendCmd(deviceAndGatewayDO, controlReq);
                break;
            //空调风向命令发送
            case ControlType.AC_WIND_DIRECTION_SEND_REQUEST:
                cmd = getAcWindDirectionSendCmd(deviceAndGatewayDO, controlReq);
                break;
            //以下为中央空调
            //中央空调温度控制
            case ControlType.CENTRAL_AC_TEMP_REQUEST:
                cmd = getCentralAcTempCmd(deviceAndGatewayDO, controlReq);
                break;
            //中央空调开机
            case ControlType.CENTRAL_AC_OPEN_REQUEST:
                cmd = getCentralAcFixedCmd(deviceAndGatewayDO, controlReq);
                break;
            //中央空调关机
            case ControlType.CENTRAL_AC_CLOSE_REQUEST:
                cmd = getCentralAcFixedCmd(deviceAndGatewayDO, controlReq);
                break;
            //中央空调制冷
            case ControlType.CENTRAL_AC_MODE_COOL_REQUEST:
                cmd = getCentralAcFixedCmd(deviceAndGatewayDO, controlReq);
                break;
            //中央空调除湿
            case ControlType.CENTRAL_AC_MODE_DEHUMIDIFY_REQUEST:
                cmd = getCentralAcFixedCmd(deviceAndGatewayDO, controlReq);
                break;
            //中央空调送风
            case ControlType.CENTRAL_AC_MODE_AIR_SUPPLY_REQUEST:
                cmd = getCentralAcFixedCmd(deviceAndGatewayDO, controlReq);
                break;
            //中央空调制热
            case ControlType.CENTRAL_AC_MODE_HOT_REQUEST:
                cmd = getCentralAcFixedCmd(deviceAndGatewayDO, controlReq);
                break;
            //中央空调风速高
            case ControlType.CENTRAL_AC_WUBD_SPEED_HIGHT_REQUEST:
                cmd = getCentralAcFixedCmd(deviceAndGatewayDO, controlReq);
                break;
            //中央空调风速中
            case ControlType.CENTRAL_AC_WUBD_SPEED_MIDDLE_REQUEST:
                cmd = getCentralAcFixedCmd(deviceAndGatewayDO, controlReq);
                break;
            //中央空调风速低
            case ControlType.CENTRAL_AC_WUBD_SPEED_LOW_REQUEST:
                cmd = getCentralAcFixedCmd(deviceAndGatewayDO, controlReq);
                break;

            //红外学习仪设置定时任务
            case ControlType.SET_TIMED_TASK:
                //设置定时任务启用或禁用状态
            case ControlType.SET_TIMED_TASK_STATUS:
                //删除定时任务
            case ControlType.DELETE_TIMED_TASK:
                cmd = getSetTimedTaskCmd(deviceAndGatewayDO, controlReq);
                break;
            default:
                break;
        }
        return cmd;
    }


    /**
     * 中央空调温度控制
     *
     * @param deviceAndGatewayDO
     * @param controlReq
     * @return
     */
    private static String getCentralAcTempCmd(DeviceAndGatewayDO deviceAndGatewayDO, ControlReq controlReq) {

        Map<String, Object> actionsMap = controlReq.getActions();
        String centralAcCode = actionsMap.get("centralAcCode").toString();
        int temp = (int) actionsMap.get("temperature");

        String controlCmd = InfraredCmdDeal.CentralAcFixedControlValue.CENTRAL_AC_TEMP;

        String centralAcTempCmd = controlCmd +
                CmdUtils.intToHexTwo(temp) +
                "01" +
                centralAcCode +
                CmdUtils.getCmdBodySum(controlCmd +
                        CmdUtils.intToHexTwo(temp) +
                        "01" +
                        centralAcCode);

        String fullCmd = getCommonCmd(centralAcTempCmd, deviceAndGatewayDO);

        return fullCmd;

    }


    /**
     * 获取中央空调固定控制命令
     *
     * @param
     * @return
     */
    private static String getCentralAcFixedCmd(DeviceAndGatewayDO deviceAndGatewayDO, ControlReq controlReq) {

        String controlType = controlReq.getControlType();
        Map<String, Object> actionsMap = controlReq.getActions();
        String centralAcCode = actionsMap.get("centralAcCode").toString();

        String controlCmd = "";

        switch (controlType) {
            case ControlType.CENTRAL_AC_OPEN_REQUEST:
                //开
                controlCmd = InfraredCmdDeal.CentralAcFixedControlValue.CENTRAL_AC_OPEN;
                break;
            case ControlType.CENTRAL_AC_CLOSE_REQUEST:
                //关
                controlCmd = InfraredCmdDeal.CentralAcFixedControlValue.CENTRAL_AC_CLOSE;
                break;
            case ControlType.CENTRAL_AC_MODE_COOL_REQUEST:
                //制冷
                controlCmd = InfraredCmdDeal.CentralAcFixedControlValue.CENTRAL_AC_MODE_COOL;
                break;
            case ControlType.CENTRAL_AC_MODE_DEHUMIDIFY_REQUEST:
                //除湿
                controlCmd = InfraredCmdDeal.CentralAcFixedControlValue.CENTRAL_AC_MODE_DEHUMIDIFY;
                break;
            case ControlType.CENTRAL_AC_MODE_AIR_SUPPLY_REQUEST:
                //送风
                controlCmd = InfraredCmdDeal.CentralAcFixedControlValue.CENTRAL_AC_MODE_AIR_SUPPLY;
                break;
            case ControlType.CENTRAL_AC_MODE_HOT_REQUEST:
                //制热
                controlCmd = InfraredCmdDeal.CentralAcFixedControlValue.CENTRAL_AC_MODE_HOT;
                break;
            case ControlType.CENTRAL_AC_WUBD_SPEED_HIGHT_REQUEST:
                //高风速
                controlCmd = InfraredCmdDeal.CentralAcFixedControlValue.CENTRAL_AC_WIND_SPEED_HIGHT;
                break;
            case ControlType.CENTRAL_AC_WUBD_SPEED_MIDDLE_REQUEST:
                //中风速
                controlCmd = InfraredCmdDeal.CentralAcFixedControlValue.CENTRAL_AC_WIND_SPEED_MIDDLE;
                break;
            case ControlType.CENTRAL_AC_WUBD_SPEED_LOW_REQUEST:
                //低风速
                controlCmd = InfraredCmdDeal.CentralAcFixedControlValue.CENTRAL_AC_WIND_SPEED_LOW;
                break;
            default:
                break;

        }

        String centralAcFixedCmd = controlCmd +
                centralAcCode +
                CmdUtils.getCmdBodySum(controlCmd + centralAcCode);

        String fullCmd = getCommonCmd(centralAcFixedCmd, deviceAndGatewayDO);

        return fullCmd;
    }

    /**
     * 空调风向命令发送
     *
     * @param deviceAndGatewayDO
     * @param controlReq
     * @return
     */
    private static String getAcWindDirectionSendCmd(DeviceAndGatewayDO deviceAndGatewayDO, ControlReq controlReq) {

        Map<String, Object> actionsMap = controlReq.getActions();
        String windDirection = actionsMap.get("windDirection").toString();
        String value = "";
        switch (windDirection) {
            //自动摆风
            case ControlType.SetWindDirection.AUTO:
                value = "00";
                break;
            //手动摆风
            case ControlType.SetWindDirection.MANUAL:
                value = "01";
                break;
            default:
                break;

        }
        String acWindDirectionCmd1To4 = InfraredCmdDeal.AcWindDirectionSend.CMD_1 +
                value +
                InfraredCmdDeal.AcWindDirectionSend.CMD_3 +
                InfraredCmdDeal.AcWindDirectionSend.CMD_4;

        String acWindDirectionCmd5 = DataTypeUtil.getAddCheckByXor(acWindDirectionCmd1To4);

        String acWindDirectionCmd = acWindDirectionCmd1To4 + acWindDirectionCmd5;

        String fullCmd = getCommonCmd(acWindDirectionCmd, deviceAndGatewayDO);

        return fullCmd;

    }

    /**
     * 空调风速命令发送
     *
     * @param deviceAndGatewayDO
     * @param controlReq
     * @return
     */
    private static String getAcWindSpeedSendCmd(DeviceAndGatewayDO deviceAndGatewayDO, ControlReq controlReq) {

        Map<String, Object> actionsMap = controlReq.getActions();
        String windSpeed = actionsMap.get("windSpeed").toString();

        String value = "";
        switch (windSpeed) {
            //自动
            case ControlType.SetWindSpeed.AUTO:
                value = "00";
                break;
            //低风速
            case ControlType.SetWindSpeed.LOW:
                value = "01";
                break;
            //中风速
            case ControlType.SetWindSpeed.MID:
                value = "02";
                break;
            //高风速
            case ControlType.SetWindSpeed.HIGH:
                value = "03";
                break;
            default:
                break;
        }

        String acWindSpeedCmd1To4 = InfraredCmdDeal.AcWindSpeedSend.CMD_1 +
                value +
                InfraredCmdDeal.AcWindSpeedSend.CMD_3 +
                InfraredCmdDeal.AcWindSpeedSend.CMD_4;

        String acWindSpeedCmd5 = DataTypeUtil.getAddCheckByXor(acWindSpeedCmd1To4);

        String acWindSpeedCmd = acWindSpeedCmd1To4 + acWindSpeedCmd5;

        String fullCmd = getCommonCmd(acWindSpeedCmd, deviceAndGatewayDO);

        return fullCmd;

    }


    /**
     * 空调温度命令发送
     *
     * @param deviceAndGatewayDO
     * @param controlReq
     * @return
     */
    private static String getAcTempSendCmd(DeviceAndGatewayDO deviceAndGatewayDO, ControlReq controlReq) {

        Map<String, Object> actionsMap = controlReq.getActions();
        int temp = (int) actionsMap.get("temperature");

        String acTempSendCmd2 = CmdUtils.intToHexTwo(temp);

        String acTempSendCmd1To4 = InfraredCmdDeal.AcTempSend.CMD_1 +
                acTempSendCmd2 +
                InfraredCmdDeal.AcTempSend.CMD_3 +
                InfraredCmdDeal.AcTempSend.CMD_4;

        String acTempSendCmd5 = DataTypeUtil.getAddCheckByXor(acTempSendCmd1To4);

        String acTempSendCmd = acTempSendCmd1To4 + acTempSendCmd5;

        String fullCmd = getCommonCmd(acTempSendCmd, deviceAndGatewayDO);

        return fullCmd;

    }

    /**
     * 空调模式命令发送
     *
     * @param deviceAndGatewayDO
     * @param controlReq
     * @return
     */
    private static String getAcModeSendCmd(DeviceAndGatewayDO deviceAndGatewayDO, ControlReq controlReq) {

        Map<String, Object> actionsMap = controlReq.getActions();
        String mode = actionsMap.get("mode").toString();

        String value = "";
        switch (mode) {
            //自动
            case ControlType.SetMode.AUTO:
                value = "00";
                break;
            //制冷
            case ControlType.SetMode.COLD:
                value = "01";
                break;
            //除湿
            case ControlType.SetMode.DEHUMIDIFICATION:
                value = "02";
                break;
            //送风
            case ControlType.SetMode.WIND:
                value = "03";
                break;
            //制热
            case ControlType.SetMode.HEAT:
                value = "04";
                break;
            default:
                break;
        }

        String acModeSendCmd1To4 = InfraredCmdDeal.AcModeSend.CMD_1 +
                value +
                InfraredCmdDeal.AcModeSend.CMD_3 +
                InfraredCmdDeal.AcModeSend.CMD_4;

        String acModeSendCmd5 = DataTypeUtil.getAddCheckByXor(acModeSendCmd1To4);

        String acModeSendCmd = acModeSendCmd1To4 + acModeSendCmd5;

        String fullCmd = getCommonCmd(acModeSendCmd, deviceAndGatewayDO);

        return fullCmd;

    }

    /**
     * 空调开关命令发送
     *
     * @param deviceAndGatewayDO
     * @param controlReq
     * @return
     */
    private static String getAcSwitchSendCmd(DeviceAndGatewayDO deviceAndGatewayDO, ControlReq controlReq) {

        Map<String, Object> actionsMap = controlReq.getActions();
        String switchState = actionsMap.get("switchState").toString();
        String value = "";
        switch (switchState) {
            case "ON":
                //开启
                value = "FF";
                break;
            case "OFF":
                //关闭
                value = "00";
                break;
            default:
                break;
        }
        String acSwitchSendCmd1To4 = InfraredCmdDeal.AcSwitchSend.CMD_1 +
                value +
                InfraredCmdDeal.AcSwitchSend.CMD_3 +
                InfraredCmdDeal.AcSwitchSend.CMD_4;

        String acSwitchSendCmd5 = DataTypeUtil.getAddCheckByXor(acSwitchSendCmd1To4);

        String acSwitchSendCmd = acSwitchSendCmd1To4 + acSwitchSendCmd5;

        String fullCmd = getCommonCmd(acSwitchSendCmd, deviceAndGatewayDO);

        return fullCmd;
    }

    /**
     * 红外信号学习
     *
     * @param deviceAndGatewayDO
     * @param controlReq
     * @return
     */
    private static String getInfraredStudyCmd(DeviceAndGatewayDO deviceAndGatewayDO, ControlReq controlReq) {

        Map<String, Object> actionsMap = controlReq.getActions();
        //学习按钮的编号
        String studyNumber = actionsMap.get("studyNumber").toString();

        String infraredStudyCmd2 = CmdUtils.intToHexTwo(Integer.parseInt(studyNumber));

        String infraredStudyCmd1To4 = InfraredCmdDeal.InfraredStudy.CMD_1 +
                infraredStudyCmd2 +
                InfraredCmdDeal.InfraredStudy.CMD_3 +
                InfraredCmdDeal.InfraredStudy.CMD_4;

        String infraredStudyCmd5 = DataTypeUtil.getAddCheckByXor(infraredStudyCmd1To4);

        String infraredStudyCmd = infraredStudyCmd1To4 + infraredStudyCmd5;

        String fullCmd = getCommonCmd(infraredStudyCmd, deviceAndGatewayDO);

        return fullCmd;
    }


    private static String getInfraredSendCmd(DeviceAndGatewayDO deviceAndGatewayDO, ControlReq controlReq) {

        Map<String, Object> actionsMap = controlReq.getActions();
        //学习按钮的编号
        String studyNumber = actionsMap.get("studyNumber").toString();

        String infraredSendCmd2 = CmdUtils.intToHexTwo(Integer.parseInt(studyNumber));

        String infraredSendCmd1To4 = InfraredCmdDeal.InfraredSend.CMD_1 +
                infraredSendCmd2 +
                InfraredCmdDeal.InfraredSend.CMD_3 +
                InfraredCmdDeal.InfraredSend.CMD_4;

        String infraredSendCmd5 = DataTypeUtil.getAddCheckByXor(infraredSendCmd1To4);

        String infraredSendCmd = infraredSendCmd1To4 + infraredSendCmd5;

        String fullCmd = getCommonCmd(infraredSendCmd, deviceAndGatewayDO);

        return fullCmd;

    }


    /**
     * 处理命令的公共部分
     * 帧头、数据长度、命令标识写 OD 、目标地址形式、网关MAC、节点MAC、数据长度、校验和、帧尾
     *
     * @param
     * @param infraredCmd,deviceAndGatewayDO
     * @return
     */
    private static String getCommonCmd(String infraredCmd, DeviceAndGatewayDO deviceAndGatewayDO) {

        String gatewayMac = deviceAndGatewayDO.getGatewayMac();
        String deviceMac = deviceAndGatewayDO.getZigbeeMac();

        String infraredCommonCmd7 = CmdUtils.getDateLength(infraredCmd);

        String infraredCommonCmd3To8 = InfraredCmdDeal.InfraredCommon.CMD_3 +
                InfraredCmdDeal.InfraredCommon.CMD_4 +
                gatewayMac +
                deviceMac +
                infraredCommonCmd7 +
                infraredCmd;

        String infraredCommonCmd2 = CmdUtils.getDateLength(infraredCommonCmd3To8);

        String infraredCommonCmd9 = CmdUtils.getCmdBodySum(infraredCommonCmd3To8);

        String fullCmd = InfraredCmdDeal.InfraredCommon.CMD_1 +
                infraredCommonCmd2 +
                infraredCommonCmd3To8 +
                infraredCommonCmd9 +
                InfraredCmdDeal.InfraredCommon.CMD_10;

        return fullCmd;

    }

    /**
     * 设置定时任务，修改状态和删除任务仅修改使能位的数据
     *
     * @param deviceAndGatewayDO deviceAndGatewayDO
     * @param controlReq         controlReq
     * @return fullcmd
     */
    private static String getSetTimedTaskCmd(DeviceAndGatewayDO deviceAndGatewayDO, ControlReq controlReq) {
        Map<String, Object> actionsMap = controlReq.getActions();

        //是否启用
        int taskEnable = Integer.parseInt(actionsMap.get("taskEnable").toString());


        //开始时间
        String startTime = actionsMap.get("startTime").toString();
        int hour = Integer.parseInt(startTime.substring(0, startTime.indexOf(':')));
        int minute = Integer.parseInt(startTime.substring(startTime.indexOf(':') + 1));
        String startTimeHex = CmdUtils.intToHexTwo(hour) + CmdUtils.intToHexTwo(minute) + "00";

        //重发间隔
        int taskInterval = Integer.parseInt(actionsMap.get("taskInterval").toString());
        String taskIntervalHex = CmdUtils.intToHexFour(taskInterval);
        taskIntervalHex = taskIntervalHex.substring(2, 4) + taskIntervalHex.substring(0, 2);

        //重发次数
        int repeatTime = Integer.parseInt(actionsMap.get("repeatTime").toString());
        //控制类型
        int controlType = Integer.parseInt(actionsMap.get("controlType").toString());

        //控制参数
        String acSwitch = actionsMap.get("acSwitch").toString();
        acSwitch = AcSwitchEnum.getValueByName(acSwitch);
        String acMode = actionsMap.get("acMode").toString();
        acMode = AcModeEnum.getValueByName(acMode);
        String acWindSpeed = actionsMap.get("acWindSpeed").toString();
        acWindSpeed = AcWindSpeedEnum.getValueByName(acWindSpeed);
        String acWindDirection = actionsMap.get("acWindDirection").toString();
        acWindDirection = AcWindDirectionEnum.getValueByName(acWindDirection);
        int acTemp = Integer.parseInt(actionsMap.get("acTemp").toString());
        String acTempStr = "0" + (acTemp * 10);
        acTempStr = acTempStr.substring(2, 4) + acTempStr.substring(0, 2);


        String controlParams = acSwitch + acMode + acWindSpeed + acWindDirection + acTempStr;


        //从定时使能到控制参数结束
        String sendCmd10To15 = CmdUtils.intToHexTwo(taskEnable) + CmdUtils.intToHexTwo(repeatTime) + taskIntervalHex
                + startTimeHex + CmdUtils.intToHexTwo(controlType) + controlParams;

        return getFullSetTimedTaskCmd(sendCmd10To15, deviceAndGatewayDO, controlReq);
    }

    /**
     * 定时任务公共部分
     *
     * @param setTimeTaskCmd     定时任务内容
     * @param deviceAndGatewayDO deviceAndGatewayDO，获取网关MAC和红外学习仪MAC
     * @param controlReq         controlReq，获取任务序号
     * @return fullcmd
     */
    private static String getFullSetTimedTaskCmd(String setTimeTaskCmd, DeviceAndGatewayDO deviceAndGatewayDO, ControlReq controlReq) {
        int taskIndex = Integer.parseInt(controlReq.getActions().get("taskIndex").toString());
        //任务序号，为1-3，分别对应子索引2-4
        String taskIndexHexStr = CmdUtils.intToHexTwo(taskIndex + 1);

        String fullCmd = "0201" + deviceAndGatewayDO.getGatewayMac() + deviceAndGatewayDO.getZigbeeMac() + "1778" + taskIndexHexStr
                + CmdUtils.getDateLength(setTimeTaskCmd) + setTimeTaskCmd;

        return "2A" + CmdUtils.getDateLength(fullCmd) + fullCmd + CmdUtils.getCmdBodySum(fullCmd) + "23";
    }
}
